//
// Created by ziya on 2021/10/17.
//

#include <zconf.h>
#include "hpp/JavaThread.h"
#include "hpp/TaskPool.h"
#include "hpp/ThreadPool.h"
#include "hpp/ObjectMonitor.h"
#include <pthread.h>
#include "hpp/ParkEvent.h"

using namespace std;

extern TaskPool taskPool;
extern ThreadPool threadPool;
ObjectMonitor* monitor = new ObjectMonitor;

ParkEvent* JavaThread::parkEvent = new ParkEvent;

void* thread_do(void* thread){

    JavaThread* jThread = (JavaThread *)thread;

    pthread_mutex_lock(jThread->lock);

    jThread->threadState = INITIALIZED;
//    printf("%s %s %d \n",jThread->_name.c_str(),"阻塞11",jThread->condt);

    pthread_cond_wait(jThread->condt,jThread->lock);
    printf("%s %s \n",jThread->_name.c_str(),"释放");
    pthread_mutex_unlock(jThread->lock);

    while (true){


        pthread_mutex_lock(taskPool._lock);

        while (0 == taskPool.task_count() ){

            INFO_PRINT("[%s] 暂时无任务，进入阻塞 \n",jThread->_name.c_str());

            pthread_cond_wait(taskPool._condt,taskPool._lock);

            printf("%s: \n",jThread->_name.c_str());

            if (threadPool._live_size > threadPool._core_size) {
                INFO_PRINT("[%s] 销毁\n", jThread->_name.c_str());

                threadPool._live_size--;

                // 这里一定要记得解锁。否则第二次销毁的时候，wait内部是上锁的
                pthread_mutex_unlock(taskPool._lock);

                pthread_exit(NULL);
            }


        }

        Task *task = taskPool.DequeueTask() ;

        taskPool.DescTaskCount();

        pthread_mutex_unlock(taskPool._lock);

        pthread_mutex_lock(threadPool._lock);

        threadPool._busy_size++ ;
        INFO_PRINT("[%s]线程池数据: core size=%d, live size=%d, busy size=%d, max size=%d\n",
                   jThread->_name.c_str(), threadPool._core_size, threadPool._live_size, threadPool._busy_size, threadPool._max_size);
        pthread_mutex_unlock(threadPool._lock);

        monitor->enter(jThread);

        task->do_some_thing();

        sleep(4);

        monitor->exit(jThread);

        INFO_PRINT("%s: do some thing \n",jThread->_name.c_str());

        pthread_mutex_lock(threadPool._lock);

        threadPool._busy_size-- ;
        INFO_PRINT("[%s]线程池数据: core size=%d, live size=%d, busy size=%d, max size=%d\n",
                   jThread->_name.c_str(), threadPool._core_size, threadPool._live_size, threadPool._busy_size, threadPool._max_size);
        pthread_mutex_unlock(threadPool._lock);


    }


//    pthread_exit(jThread->tid);

}

 JavaThread::JavaThread(string name){

     _name = name;

     pthread_mutex_init(lock,NULL);

     pthread_cond_init(condt,NULL);

     pthread_attr_init(attr);

     pthread_attr_setdetachstate(attr,PTHREAD_CREATE_DETACHED);

     pthread_create(tid, attr, thread_do, this);

     threadState = ALLOCATED;

     printf("%s %s \n",name.c_str(),"初始化");

     pthread_attr_destroy(attr);
//
}

JavaThread::JavaThread(int idx) {

    stringstream ss;
    ss << "t";
    ss << idx;
    _name = ss.str();

    pthread_mutex_init(lock, NULL);
    pthread_cond_init(condt, NULL);

    pthread_attr_t attr;
    pthread_attr_init(&attr);
    pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_DETACHED);

    threadState = ALLOCATED;

    pthread_create(tid, &attr, thread_do, this);

    pthread_attr_destroy(&attr);
}

void JavaThread::run() {
    while (true){
        if(threadState == INITIALIZED){
            pthread_cond_signal(condt);
            printf("%s %s  \n",_name.c_str(),"唤醒");
            break;
        }
    }
}



